<template>
  <div class="data-management">
    <!-- 上部分：时间筛选 -->
    <div class="filter-bar">
      <div class="time-filter">
        <span class="filter-label">开始时间：</span>
        <el-date-picker
            v-model="startTime"
            type="datetime"
            placeholder="2025-07-16 00:00:00"
            format="YYYY-MM-DD HH:mm:ss"
            value-format="YYYY-MM-DD HH:mm:ss"
            :disabled-date="disabledStartDate"
            @change="onStartTimeChange"
            size="default"
            style="width: 200px"
        />
        <span class="filter-label" style="margin-left: 30px">结束时间：</span>
        <el-date-picker
            v-model="endTime"
            type="datetime"
            placeholder="2025-07-16 00:00:00"
            format="YYYY-MM-DD HH:mm:ss"
            value-format="YYYY-MM-DD HH:mm:ss"
            :disabled-date="disabledEndDate"
            @change="onEndTimeChange"
            size="default"
            style="width: 200px"
        />
        <el-button type="primary" @click="searchData" style="margin-left: 20px">
          查询
        </el-button>
        <el-button @click="resetFilter" style="margin-left: 10px">
          重置
        </el-button>
      </div>
    </div>

    <!-- 下部分：数据表格 -->
    <div class="table-section">
      <div class="table-header">
        <h3>采集数据列表</h3>
        <div class="table-controls">
          <el-button size="small" @click="refreshData" type="success">
            刷新
          </el-button>
          <el-button
              size="small"
              type="danger"
              @click="batchDeleteData"
              :disabled="selectedRows.length === 0"
          >
            批量删除
          </el-button>
        </div>
      </div>

      <div class="table-container">
        <el-table
            ref="dataTable"
            :data="paginatedData"
            style="width: 100%; height: 100%"
            stripe
            :header-cell-style="{
            background: '#f8f9fa',
            color: '#333',
            fontWeight: '500',
            textAlign: 'center',
          }"
            :cell-style="{ textAlign: 'center' }"
            border
            @selection-change="handleSelectionChange"
            @sort-change="handleSortChange"
            v-loading="loading"
        >
          <el-table-column type="selection" width="50" align="center" />
          <el-table-column prop="dataId" label="序号" width="80" align="center" />
          <el-table-column prop="collectionTaskId" label="采集任务ID" width="80" align="center" />
          <el-table-column prop="collectionTaskName" label="采集任务名称" width="160" align="center" />
          <el-table-column
              prop="startCollectTime"
              label="开始采集时间"
              min-width="80"
              align="center"
              sortable="custom"
              :sort-orders="['descending', 'ascending']"
              :default-sort="{ prop: 'startCollectTime', order: 'descending' }"
          >
            <template #default="scope">
              <div class="time-cell">
                <el-icon><Clock /></el-icon>
                <span>{{ scope.row.startCollectTime }}</span>
              </div>
            </template>
          </el-table-column>
          <el-table-column
              prop="endCollectTime"
              label="结束采集时间"
              min-width="80"
              align="center"
          >
            <template #default="scope">
              <div class="time-cell">
                <el-icon><Clock /></el-icon>
                <span>{{ scope.row.endCollectTime }}</span>
              </div>
            </template>
          </el-table-column>
          <el-table-column
              prop="collectDuration"
              label="采集时长"
              width="140"
              align="center"
          >
            <template #default="scope">
              <el-tag size="small" type="info">{{ scope.row.collectDuration }}</el-tag>
            </template>
          </el-table-column>
          <el-table-column
              prop="isArchived"
              label="归档状态"
              width="80"
              align="center"
          >
            <template #default="scope">
              <el-tag
                  :type="scope.row.isArchived === '1' ? 'success' : 'warning'"
                  size="small"
              >
                {{ scope.row.isArchived === '1' ? "已归档" : "未归档" }}
              </el-tag>
            </template>
          </el-table-column>

          <el-table-column
              prop="storagePath"
              label="存储路径"
              min-width="80"
              align="center"
              show-overflow-tooltip
          >
            <template #default="scope">
              <span class="path-cell">{{ scope.row.storagePath }}</span>
            </template>
          </el-table-column>
          <el-table-column
              label="操作"
              width="280"
              align="center"
              fixed="right"
          >
            <template #default="scope">
              <div class="action-buttons">
                <el-button
                    size="small"
                    type="primary"
                    @click="goToDetail(scope.row)"
                >
                  查看
                </el-button>
                <el-button
                    size="small"
                    type="primary"
                    @click="goToEdit(scope.row)"
                >
                  编辑
                </el-button>
                <el-button
                    size="small"
                    type="success"
                    @click="archiveData(scope.row)"
                    :disabled="scope.row.isArchived === '1'"
                >
                  归档
                </el-button>
                <el-button
                    size="small"
                    type="danger"
                    @click="deleteData(scope.row)"
                >
                  删除
                </el-button>
              </div>
            </template>
          </el-table-column>
        </el-table>
      </div>

      <div class="pagination-container">
        <div class="pagination-info">
          <span
          >共 {{ total }} 条记录，当前显示第
            {{ (currentPage - 1) * pageSize + 1 }} -
            {{ Math.min(currentPage * pageSize, total) }} 条</span
          >
        </div>
        <el-pagination
            :current-page="currentPage"
            :page-size="pageSize"
            :page-sizes="[10, 20, 50, 100]"
            layout="sizes, prev, pager, next, jumper"
            :total="total"
            @size-change="handleSizeChange"
            @current-change="handleCurrentChange"
            size='small'
        />
      </div>
    </div>

    <!-- 归档弹窗 -->
    <el-dialog
        v-model="showArchiveDialog"
        title="数据归档"
        width="600px"
        :close-on-click-modal="false"
    >
      <div class="archive-dialog-content">
        <!-- 任务筛选区域 -->
        <div class="task-filter-section">
          <h4>选择归档任务</h4>
          <div class="filter-controls">
            <el-input
                v-model="taskFilter.taskName"
                placeholder="任务名称"
                clearable
                style="width: 200px"
            >
              <template #prefix>
                <el-icon><Search /></el-icon>
              </template>
            </el-input>
            <el-select
                v-model="taskFilter.status"
                placeholder="任务状态"
                clearable
                style="width: 120px"
            >
              <el-option label="全部状态" value="" />
              <el-option label="正常" value="0" />
              <el-option label="停用" value="1" />
            </el-select>
            <el-button @click="searchTaskList" type="primary" size="small">
              查询
            </el-button>
            <el-button @click="resetTaskFilter" type="info" size="small">
              重置
            </el-button>
          </div>
        </div>

        <!-- 任务列表 -->
        <div class="task-list-section">
          <div class="task-list-header">
            <span>任务列表 ({{ taskListTotal }} 条)</span>
            <el-button
                @click="clearTaskSelection"
                size="small"
                type="info"
                :disabled="!archiveForm.taskId"
            >
              清除选择
            </el-button>
          </div>
          <div class="task-list-container">
            <el-table
                :data="taskList"
                style="width: 100%"
                height="300"
                @row-click="onTaskRowClick"
                :row-class-name="getTaskRowClassName"
                v-loading="taskListLoading"
            >
              <el-table-column prop="taskName" label="任务名称" min-width="120">
                <template #default="scope">
                  <div class="task-name-cell">
                    <el-icon class="task-icon"><VideoPlay /></el-icon>
                    <span>{{ scope.row.taskName }}</span>
                  </div>
                </template>
              </el-table-column>
              <el-table-column prop="startTime" label="开始时间" width="140">
                <template #default="scope">
                  <span class="time-text">{{ formatTaskTime(scope.row.startTime) }}</span>
                </template>
              </el-table-column>
              <el-table-column prop="endTime" label="结束时间" width="140">
                <template #default="scope">
                  <span class="time-text">{{ formatTaskTime(scope.row.endTime) }}</span>
                </template>
              </el-table-column>
              <el-table-column prop="status" label="状态" width="80" align="center">
                <template #default="scope">
                  <el-tag
                      :type="getTaskStatusType(scope.row.status)"
                      size="small"
                  >
                    {{ getTaskStatusText(scope.row.status) }}
                  </el-tag>
                </template>
              </el-table-column>
            </el-table>
          </div>
          <!-- 任务分页 -->
          <div class="task-pagination">
            <el-pagination
                :current-page="taskCurrentPage"
                :page-size="taskPageSize"
                :page-sizes="[5, 10, 20, 50]"
                layout="sizes, prev, pager, next, jumper"
                :total="taskListTotal"
                @size-change="handleTaskSizeChange"
                @current-change="handleTaskCurrentChange"
                size="small"
            />
          </div>
        </div>

        <!-- 归档表单 -->
        <div class="archive-form-section">
          <h4>归档信息</h4>
          <el-form
              :model="archiveForm"
              label-width="100px"
              :rules="archiveRules"
              ref="archiveFormRef"
          >
            <el-form-item label="选择任务" prop="taskId">
              <el-input
                  v-model="archiveForm.taskName"
                  placeholder="请从上方列表选择任务"
                  readonly
                  style="width: 100%"
              >
                <template #suffix>
                  <el-icon v-if="archiveForm.taskId" class="selected-icon"><Check /></el-icon>
                </template>
              </el-input>
            </el-form-item>
          </el-form>
        </div>
      </div>

      <template #footer>
        <el-button @click="showArchiveDialog = false">取消</el-button>
        <el-button
            type="primary"
            @click="confirmArchive"
            :loading="archiveLoading"
            :disabled="!archiveForm.taskId"
        >
          确认归档
        </el-button>
      </template>
    </el-dialog>

    <!--编辑弹窗 -->
    <el-dialog
        v-model="showEditDialog"
        title="编辑"
        width="80%"
        height="80%"
        :close-on-click-modal="false"
        style="max-height: 90vh;"
    >
      <!-- 选项卡 -->
      <el-tabs class="data-management-tab-container" v-model="activeTab" type="border-card">
        <div>
          <!-- 视频数据编辑选项卡 -->
          <el-tab-pane label="视频数据编辑" name="video">
              <!-- 视频文件列表 -->
              <div v-if="videoFiles.length > 0" class="file-selection-section">
                <div class="section-header">
                  <h3>视频文件列表</h3>
                  <span class="file-count">共 {{ videoFiles.length }} 个文件，已选择 {{ selectedVideoFiles.length }} 个</span>
                </div>
                <div class="scroll-wrapper"  style="height:530px;">
                  <div class="data-grid video-files">
                    <div
                        v-for="file in videoFiles"
                        :key="file.fileName"
                        class="data-card"
                        :class="{ 'selected': selectedVideoFiles.includes(file.fileName) }"
                        @click="toggleVideoFileSelection(file.fileName)"
                    >
                      <div class="card-checkbox">
                        <input
                            type="checkbox"
                            :checked="selectedVideoFiles.includes(file.fileName)"
                            @change.stop="toggleVideoFileSelection(file.fileName)"
                        />
                        <span class="checkmark"></span>
                      </div>
                      <div class="card-content">
                        <div class="file-name">{{ file.fileName }}</div>
                        <div class="file-size">{{ file.fileSize}}{{ file.fileSizeUnit}}</div>
                      </div>
                    </div>                   
                  </div>
                </div>
              </div>
              <div v-else-if="currentRow && currentRow.dataId" class="loading-state">
                <el-empty description="加载视频文件中..." :image-size="40"></el-empty>
              </div>
              <!-- 操作按钮 -->
              <div style="margin-top: 16px;text-align: center;">
                <button @click="selectVideoFile" class="top-button">上传视频</button>
                <button @click="handleCutVideoClick" class="top-button" style="margin-left: 10px" :disabled="selectedVideoFiles.length !== 1">裁剪视频</button>
                <button @click="handleConcatVideoClick" class="top-button" style="margin-left: 10px" :disabled="selectedVideoFiles.length < 2">拼接视频</button>
                <button @click="handleDownloadVideoClick" class="top-button" style="margin-left: 10px" :disabled="selectedVideoFiles.length === 0">下载视频文件</button>
              </div>
          </el-tab-pane>
          <!-- 遥测数据编辑选项卡 -->
          <el-tab-pane label="遥测数据编辑" name="telemetry">
          <!-- 遥测文件选择 -->
          <div v-if="telemetryFiles.length > 0 && showTelemetrySelection" class="file-selection-section">
            <div class="section-header">
              <h3>遥测文件选择</h3>
              <span class="file-count">共 {{ telemetryFiles.length }} 个文件，已选择 {{ selectedTelemetryFiles.length }} 个</span>
            </div>
            <div class="scroll-wrapper"  style="height:550px;">
              <div class="data-grid telemetry-files">
                <div
                    v-for="file in telemetryFiles"
                    :key="file.fileName"
                    class="data-card"
                    :class="{ 'selected': selectedTelemetryFiles.includes(file.fileName) }"
                    @click="toggleTelemetryFileSelection(file.fileName)"
                >
                  <!-- 右上角标签：根据文件名判断类型 -->
                  <el-tag type="primary" size="small" v-if="file.fileName.includes('_edit_')">
                    上传文件
                  </el-tag>
                  <el-tag type="success" size="small" v-else>
                    采集文件
                  </el-tag>
                  
                  <!-- 复选框 -->
                  <div class="card-checkbox">
                    <input
                        type="checkbox"
                        :id="`telemetry-${file.fileName}`"
                        :checked="selectedTelemetryFiles.includes(file.fileName)"
                        @change="(e) => {
                          e.stopPropagation();
                          toggleTelemetryFileSelection(file.fileName);
                        }"
                    >
                    <label :for="`telemetry-${file.fileName}`" class="custom-checkbox"></label>
                  </div>

                  <!-- 数据内容 -->
                  <div class="card-content">
                    <h3 class="data-name">{{ file.fileName }}</h3>
                    <p class="file-size">{{ file.fileSize}} KB</p>
                  </div>
                </div>
              </div>
            </div>
          </div>
          
          <div v-else-if="telemetryFiles.length === 0" class="file-selection-section">
            <el-empty description="暂无遥测数据文件" />
          </div>
          
          <!-- 裁剪遥测数据按钮 -->
          <div style="margin-top: 16px; text-align: center;">
            <el-button 
              type="primary" 
              @click="openTelemetryCropDialog"
              :disabled="selectedTelemetryFiles.length === 0"
            >
              裁剪遥测数据
            </el-button>
            <el-button 
              @click="showTelemetryUploadDialog = true"
              style="margin-left: 10px;"
            >
              上传遥测数据
            </el-button>
            <el-button 
              @click="handleDownloadTelemetryClick"
              style="margin-left: 10px;"
              :disabled="selectedTelemetryFiles.length === 0"
            >
              下载遥测数据文件
            </el-button>
          </div>
        </el-tab-pane>
        
        <!-- 用户操作记录选项卡 -->
        <el-tab-pane label="用户操作记录" name="history">
          <div class="timeline-container">
            <div style="width: 100%;display: flex;justify-content: flex-start">
              <h1 >操作记录</h1>
            </div>

            <div class="timeline" v-if="timelineItems.length>0">
              <div v-for="(item, index) in timelineItems" :key="index" class="timeline-item">
                <div class="timeline-dot"></div>
                <div class="timeline-content">
                  <div class="timeline-header">
                    <span class="editor-name">{{ item.realName }}</span>
                    <span class="action-type">{{ item.operation }}</span>
                    <button @click="viewDetails(item.filePath)" class="view-button">查看</button>
                  </div>
                  <div class="timeline-time">{{ formatTime(item.formatCreateTime) }}</div>
                </div>
              </div>
            </div>
            <el-empty description="暂无记录" v-else></el-empty>
          </div>
        </el-tab-pane>
        </div>
      </el-tabs>
    </el-dialog>

    <!--视频剪辑弹窗 -->
    <el-dialog
        v-model="showVideoEditDialog"
        title="视频剪辑"
        width="60%"
        :close-on-click-modal="false"
        @open="handleVideoEditOpen"
    >
      <VideoCutEditor v-if="selectedVideoFile.fileName" :video="selectedVideoFile"></VideoCutEditor>
    </el-dialog>

    <!--视频拼接弹窗 -->
    <el-dialog
        v-model="showVideoConcatDialog"
        title="视频拼接"
        width="60%"
        :close-on-click-modal="false"
    >
      <!-- 将选中的文件名转换为完整的视频对象数组 -->
      <VideoConcatEditor :videos="selectedVideoFiles.map(fileName => videoFiles.find(file => file.fileName === fileName)).filter(Boolean)"></VideoConcatEditor>
    </el-dialog>

    <!--视频上传弹窗 -->
    <el-dialog
        v-model="showVideoFileDialog"
        title="视频上传"
        width="50%"
        :close-on-click-modal="false"
        @close="handleVideoUploadClose"
    >
      <div class="video-upload-container">
        <!-- 1. 文件选择区域 -->
        <div class="file-select-section" v-if="!uploading && !uploadResult">
          <el-upload
              ref="videoUploadRef"
              action="#"
              :auto-upload="false"
              :on-change="handleFileSelect"
              :file-list="selectedFiles"
              accept="video/mp4"
              class="upload-demo"
          >
            <el-button size="default" type="primary">
              <el-icon><Upload /></el-icon> 选择视频文件
            </el-button>
            <div class="upload-tip" style="margin-top: 10px;margin-left: 10px">
              支持格式：MP4 | 单个文件最大支持 2GB
            </div>
            <!-- 已选文件提示 -->
            <div v-if="selectedFiles.length" class="selected-file-tip" style="margin-top: 10px; color: #666;">
              已选择：{{ selectedFiles[0].name }}（{{ formatFileSize(selectedFiles[0].size) }}）
            </div>
          </el-upload>
        </div>

        <!-- 2. 上传进度区域 -->
        <div class="upload-progress-section" v-if="uploading && !uploadResult">
          <div class="upload-status" style="margin-top: 15px; text-align: center;">
            {{ uploadStatusText }}
          </div>
          <div class="upload-controls" style="margin-top: 20px; text-align: center;">
            <el-button size="small" type="text" @click="cancelUpload" :disabled="uploadProgress === 100">
              取消上传
            </el-button>
          </div>
        </div>

        <!-- 3. 上传结果提示 -->
        <div class="upload-result-section" v-if="uploadResult !== null">
          <div class="result-icon" :class="uploadResult.success ? 'success' : 'error'">
            <el-icon v-if="uploadResult.success"><Check /></el-icon>
            <el-icon v-else><Close /></el-icon>
          </div>
          <div class="result-message" style="margin-top: 15px; text-align: center; font-size: 14px;">
            {{ uploadResult.message }}
          </div>
          <div class="result-controls" style="margin-top: 20px; text-align: center;">
            <el-button size="small" type="primary" @click="resetUpload">
              {{ uploadResult.success ? '继续上传' : '重新上传' }}
            </el-button>
          </div>
        </div>
      </div>

      <template #footer>
        <el-button @click="showVideoFileDialog = false" :disabled="uploading">取消</el-button>
        <el-button
            type="primary"
            @click="submitUpload"
            :disabled="!selectedFiles.length || uploading || uploadResult?.success"
        >
          确认上传
        </el-button>
      </template>
    </el-dialog>
    
    <!-- 裁剪遥测数据弹窗 -->
    <el-dialog
        v-model="showTelemetryCropDialog"
        title="裁剪遥测数据"
        width="90%"
        :close-on-click-modal="false"
    >
      <div class="telemetry-crop-container" style="display: flex; flex-direction: column; height: 70vh;">
        <!-- 顶部工具栏 -->
        <div class="crop-toolbar" style="display: flex; justify-content: space-between; align-items: center; margin-bottom: 16px;">
          <div class="toolbar-left">
            <span class="chart-info">共显示 {{ selectedTelemetryFiles.length }} 个文件的图表</span>
          </div>
          <div class="toolbar-right">
            <span class="toolbar-label">窗口布局</span>
            <el-select
              v-model="windowLayout"
              size="small"
              style="width: 120px; margin-left: 8px;"
            >
              <el-option label="每行2路" value="2" />
              <el-option label="每行3路" value="3" />
              <el-option label="每行4路" value="4" />
            </el-select>
          </div>
        </div>
        
        <!-- 图表显示区域 -->
        <div class="chart-section" style="flex: 1; overflow-y: auto; background: white; border-radius: 8px; border: 1px solid #e8e8e8;">
          <div class="chart-grid" :style="chartGridStyle">
            <div v-for="fileName in selectedTelemetryFiles" :key="fileName" class="chart-item">
              <div class="chart-item-header">
                <span class="chart-file-name">{{ fileName }}</span>
                <div style="display: flex; align-items: center; gap: 10px;">
                  <span class="chart-data-count">数据点：{{ telemetryDataByFile[fileName]?.length || 0 }} 个</span>
                  <el-button 
                    type="primary" 
                    size="small"
                    @click="downloadChartImage(fileName)"
                    title="下载图表"
                  >
                    下载
                  </el-button>
                </div>
              </div>
              <div v-if="telemetryDataByFile[fileName] && telemetryDataByFile[fileName].length > 0" class="chart-container" :data-chart-file="fileName">
                <HistoricalChart
                  :historical-data="filteredTelemetryDataByFile[fileName] || telemetryDataByFile[fileName]"
                  :ref="el => historicalChartRefs[fileName] = el"
                  :current-playback-time="timeSliderValues[1]"
                  :start-time="timeSliderValues[0]"
                  :is-playing="true"
                />
              </div>
              <div v-else class="no-telemetry">
                <el-empty description="文件无有效数据" :image-size="40">
                </el-empty>
              </div>
            </div>
          </div>
        </div>
        
        <!-- 时间选择区域 -->
        <div class="time-selection" style="margin-top: 16px;">
          <div style="margin-bottom: 16px;">裁剪时间段：</div>
          <el-slider
            v-model="timeSliderValues"
            :min="timeRangeMin"
            :max="timeRangeMax"
            range
            :format-tooltip="formatSliderTooltip"
            @change="handleSliderChange"
            style="margin-bottom: 16px;"
          />
          <div style="display: flex; gap: 16px; align-items: center;">
            <span>开始时间：</span>
            <el-input v-model="cropStartTime" placeholder="HH:mm:ss:SSS" style="width: 200px;" readonly />
            <span>结束时间：</span>
            <el-input v-model="cropEndTime" placeholder="HH:mm:ss:SSS" style="width: 200px;" readonly />
          </div>
        </div>
      </div>
      
      <template #footer>
        <el-button @click="showTelemetryCropDialog = false">取消</el-button>
        <el-button type="primary" @click="confirmCropTelemetry">确认裁剪</el-button>
      </template>
    </el-dialog>
    
    <el-dialog
        v-model="detailsVisible"
        title="视频"
        width="38%"
        :close-on-click-modal="false"
        @open="handleVideoEditOpen"
    >
      <video :src="videoPath+videoUrl"  controls style="width: 700px;text-align: center"></video>
    </el-dialog>

    <!-- 裁剪结果对话框 -->
    <el-dialog
      v-model="showCropResultDialog"
      title="裁剪成功"
      width="40%"
      :close-on-click-modal="false"
    >
      <div class="crop-result-content">
        <div class="result-item">
          <div class="result-label">裁剪时间范围：</div>
          <div class="result-value">{{ cropResultData.timeRange }}</div>
        </div>
        <div class="result-item">
          <div class="result-label">裁剪遥测文件：</div>
          <div class="result-value">
            <ul class="file-list">
              <li v-for="file in cropResultData.telemetryFiles" :key="file">{{ file }}</li>
            </ul>
          </div>
        </div>
        <div class="result-item">
          <div class="result-label">裁剪后生成的新文件：</div>
          <div class="result-value">
            <span>{{ cropResultData.newFilePath.split('/').pop() }}</span>
            <a 
              :href="API_CONFIG.IMAGE_URL + cropResultData.newFilePath" 
              target="_blank" 
              style="margin-left: 10px; color: #409eff; text-decoration: none;"
              >下载</a
            >
          </div>
        </div>
      </div>
      <template #footer>
        <el-button @click="showCropResultDialog = false">关闭</el-button>
      </template>
    </el-dialog>

    <!-- 遥测数据上传弹窗 -->
    <el-dialog
        v-model="showTelemetryUploadDialog"
        title="上传遥测数据"
        width="50%"
        :close-on-click-modal="false"
        @close="handleTelemetryUploadClose"
    >
      <div class="telemetry-upload-container">
        <!-- 1. 文件选择区域 -->
        <div class="file-select-section" v-if="!telemetryUploading && !telemetryUploadResult">
          <el-upload
              ref="telemetryUploadRef"
              action="#"
              :auto-upload="false"
              :on-change="handleTelemetryFileSelect"
              :file-list="selectedTelemetryFilesUpload"
              multiple
              accept=".txt"
              class="upload-demo"
          >
            <el-button size="default" type="primary">
              <el-icon><Upload /></el-icon> 选择TXT文件
            </el-button>
            <div class="upload-tip" style="margin-top: 10px;margin-left: 10px">
              支持格式：TXT | 单个文件最大支持 300MB | 最多上传 20 个文件
            </div>
            <!-- 已选文件列表 -->
            <div v-if="selectedTelemetryFilesUpload.length" class="selected-file-list" style="margin-top: 15px;">
              <div class="selected-file-header" style="font-weight: 500; margin-bottom: 8px;">
                已选择 {{ selectedTelemetryFilesUpload.length }} 个文件：
              </div>
              <div class="selected-file-items">
                <div v-for="file in selectedTelemetryFilesUpload" :key="file.uid" class="file-item">
                  <span class="file-name">{{ file.name }}</span>
                  <span class="file-size">({{ formatTelemetryFileSize(file.size) }})</span>
                </div>
              </div>
            </div>
          </el-upload>
        </div>

        <!-- 2. 上传进度区域 -->
        <div class="upload-progress-section" v-if="telemetryUploading && !telemetryUploadResult">
          <el-progress :percentage="telemetryUploadProgress" status="success" style="margin-top: 20px;" />
          <div class="upload-status" style="margin-top: 15px; text-align: center;">
            {{ telemetryUploadStatusText }}
          </div>
          <div class="upload-controls" style="margin-top: 20px; text-align: center;">
            <el-button size="small" type="text" @click="cancelTelemetryUpload" :disabled="telemetryUploadProgress === 100">
              取消上传
            </el-button>
          </div>
        </div>

        <!-- 3. 上传结果提示 -->
        <div class="upload-result-section" v-if="telemetryUploadResult !== null">
          <div class="result-icon" :class="telemetryUploadResult.success ? 'success' : 'error'">
            <el-icon v-if="telemetryUploadResult.success"><Check /></el-icon>
            <el-icon v-else><Close /></el-icon>
          </div>
          <div class="result-message" style="margin-top: 15px; text-align: center; font-size: 14px;">
            {{ telemetryUploadResult.message }}
          </div>
          <div class="result-controls" style="margin-top: 20px; text-align: center;">
            <el-button size="small" type="primary" @click="resetTelemetryUpload">
              {{ telemetryUploadResult.success ? '继续上传' : '重新上传' }}
            </el-button>
          </div>
        </div>
      </div>

      <template #footer>
        <el-button @click="showTelemetryUploadDialog = false" :disabled="telemetryUploading">取消</el-button>
        <el-button
            type="primary"
            @click="submitTelemetryUpload"
            :disabled="!selectedTelemetryFilesUpload.length || telemetryUploading || telemetryUploadResult?.success"
        >
          确认上传
        </el-button>
      </template>
    </el-dialog>

    <!-- 视频类型选择对话框 -->
    <el-dialog
      v-model="showVideoTypeDialog"
      title="选择视频格式"
      width="400px"
      :close-on-click-modal="false"
    >
      <div class="video-type-dialog-content">
        <p style="margin-bottom: 16px;">请选择要下载的视频文件格式：</p>
        <el-radio-group v-model="selectedVideoType" class="video-type-radio-group">
          <el-radio v-for="option in videoTypeOptions" :key="option.value" :label="option.value">
            {{ option.label }}
          </el-radio>
        </el-radio-group>
      </div>
      <template #footer>
        <el-button @click="showVideoTypeDialog = false">取消</el-button>
        <el-button type="primary" @click="confirmVideoTypeAndDownload">确认下载</el-button>
      </template>
    </el-dialog>
  </div>
</template>

<script setup>
import { ref, onMounted, computed, watch, nextTick } from "vue";
import { useRouter } from "vue-router";
import {API_CONFIG, dataAPI, taskAPI, videoDataAPI, telemetryDataListAPI, fileAPI} from '../api/index.js';
import VideoCutEditor from '../components/VideoCutEditor.vue'
import VideoConcatEditor from '../components/VideoConcatEditor.vue'
import { Upload, Check, Close, Clock, Search, VideoPlay } from "@element-plus/icons-vue";
import { ElMessage, ElMessageBox } from "element-plus";
import HistoricalChart from "../components/charts/HistoricalChart.vue";
import request from '../api/request.js';
const videoPath = ref(API_CONFIG.IMAGE_URL);
const router = useRouter();

// 编辑相关
const showEditDialog = ref(false);
const currentRow = ref({});
const showVideoEditDialog = ref(false);
const showVideoConcatDialog = ref(false);
const editDialogRef = ref(null);
const activeTab = ref('video'); // 默认显示视频数据编辑选项卡

// 遥测数据相关
const telemetryFiles = ref([]);
const selectedTelemetryFiles = ref([]);
const showTelemetrySelection = ref(true);
const telemetryDataByFile = ref({}); // 存储每个文件的遥测数据
const historicalChartRefs = ref({}); // 存储图表引用

// 下载图表为图片
const downloadChartImage = (fileName) => {
  try {
    // 获取组件实例
    const chartComponent = historicalChartRefs.value?.[fileName];
    let actualChart = null;
    
    // 优先尝试通过$refs.chartRef获取图表实例
    if (chartComponent && chartComponent.$refs && chartComponent.$refs.chartRef) {
      actualChart = chartComponent.$refs.chartRef;
    }
    
    // 如果找到图表实例并有getDataURL方法，尝试使用echarts原生方法导出
    if (actualChart && typeof actualChart.getDataURL === 'function') {
      const url = actualChart.getDataURL({
        type: 'png',
        pixelRatio: 2,
        backgroundColor: '#fff'
      });
      
      // 创建下载链接
      const link = document.createElement('a');
      link.download = `${fileName}_chart.png`;
      link.href = url;
      document.body.appendChild(link);
      link.click();
      document.body.removeChild(link);
      
      ElMessage.success('图表下载成功');
    } else {      
      
      ElMessage.warning('图表尚未准备就绪或不支持下载功能，请稍候再尝试。');
    }
  } catch (error) {
    ElMessage.error('图表下载失败');
  }
};

// 裁剪遥测数据弹窗相关
const showTelemetryCropDialog = ref(false); // 控制裁剪弹窗显示
const cropStartTime = ref(''); // 裁剪开始时间
const cropEndTime = ref(''); // 裁剪结束时间
const windowLayout = ref('2'); // 图表布局，默认为每行2个

// 时间滑块相关
const timeRangeMin = ref(0); // 最小时间戳
const timeRangeMax = ref(0); // 最大时间戳
const timeSliderValues = ref([0, 0]); // 滑块当前值数组 [start, end]

// 裁剪结果对话框相关
const showCropResultDialog = ref(false); // 控制裁剪结果对话框显示
const cropResultData = ref({
  timeRange: '', // 裁剪时间范围
  telemetryFiles: [], // 裁剪的遥测文件列表
  newFilePath: '' // 裁剪后生成的新文件路径
});

// 视频上传相关
const showVideoFileDialog = ref(false);
const videoUploadRef = ref(null);
const selectedFiles = ref([]);
const uploading = ref(false);
const uploadProgress = ref(0);
const uploadStatusText = ref("");
const uploadResult = ref(null);
const abortController = ref(null);

// 视频文件列表相关
const videoFiles = ref([]);
const selectedVideoFiles = ref([]);
const selectedVideoFile = ref({});

// 视频类型选择相关
const showVideoTypeDialog = ref(false);
const selectedVideoType = ref('mp4');
const videoTypeOptions = ref([
  { label: 'MP4', value: 'mp4' },
  { label: 'AVI', value: 'avi' },
  { label: 'WMV', value: 'wmv' },
  { label: 'MKV', value: 'mkv' },
  { label: 'FLV', value: 'flv' }
]);

// 遥测数据上传相关
const showTelemetryUploadDialog = ref(false);
const telemetryUploadRef = ref(null);
const selectedTelemetryFilesUpload = ref([]);
const telemetryUploading = ref(false);
const telemetryUploadProgress = ref(0);
const telemetryUploadStatusText = ref("");
const telemetryUploadResult = ref(null);
const telemetryAbortController = ref(null);

// 时间轴数据
const timelineItems = ref([]);
const detailsVisible = ref(false);
const videoUrl = ref('');
const uploadVideoUrl = ref('');
// 表格相关
const startTime = ref("");
const endTime = ref("");
const currentPage = ref(1);
const pageSize = ref(15);
const total = ref(0);
const selectedRows = ref([]);
const loading = ref(false);
const dataTable = ref();

// 排序相关
const sortBy = ref("startCollectTime");
const sortOrder = ref("descending");

// 表格数据
const tableData = ref([]);
const paginatedData = computed(() => tableData.value);

// 归档相关
const showArchiveDialog = ref(false);
const archiveLoading = ref(false);
const archiveFormRef = ref();
const archiveForm = ref({
  taskId: "",
  taskName: "",
  dataId: ""
});

// 任务相关
const taskList = ref([]);
const taskListLoading = ref(false);
const taskListTotal = ref(0);
const taskCurrentPage = ref(1);
const taskPageSize = ref(10);
const taskFilter = ref({
  taskName: '',
  status: ''
});
const taskNameOptions = ref([]);

// 编辑页面跳转
const goToEdit = (row) => {
  showEditDialog.value = true;
  currentRow.value = {...row};
  getVideoList();
  loadTelemetryFiles();
};

// 遥测数据上传相关函数
// 处理遥测文件选择
const handleTelemetryFileSelect = (uploadFile, fileList) => {
  // 限制文件数量不超过20个
  if (fileList.length > 20) {
    ElMessage.warning('最多只能上传20个文件');
    selectedTelemetryFilesUpload.value = fileList.slice(-20);
    return;
  }
  
  // 限制文件大小不超过300MB
  const fileSizeLimit = 300 * 1024 * 1024; // 300MB
  const oversizedFile = fileList.find(file => file.size > fileSizeLimit);
  if (oversizedFile) {
    ElMessage.warning(`文件 ${oversizedFile.name} 超过300MB大小限制`);
    return;
  }
  
  selectedTelemetryFilesUpload.value = fileList;
};

// 提交遥测文件上传
const submitTelemetryUpload = async () => {
  if (!selectedTelemetryFilesUpload.value.length) {
    ElMessage.warning('请先选择文件');
    return;
  }
  
  try {
    telemetryUploading.value = true;
    telemetryUploadProgress.value = 0;
    telemetryUploadStatusText.value = '准备上传...';
    telemetryUploadResult.value = null;
    
    // 创建新的AbortController
    telemetryAbortController.value = new AbortController();
    
    // 准备FormData
    const formData = new FormData();
    selectedTelemetryFilesUpload.value.forEach(file => {
      formData.append('file', file.raw);
    });
    
    // 添加path参数
    const savePath = telemetryFiles.value[0].savePath || '';
    formData.append('path', savePath);
    
    telemetryUploadStatusText.value = '正在上传文件...';
    
    // 调用API上传文件 - 注意：不要手动设置Content-Type，让浏览器自动处理（包括boundary）
    const response = await request.post(API_CONFIG.ENDPOINTS.UPLOAD_TELEMETRY_TXT, formData, {
      onUploadProgress: (progressEvent) => {
        if (progressEvent.total) {
          telemetryUploadProgress.value = Math.round((progressEvent.loaded * 100) / progressEvent.total);
        }
      },
      signal: telemetryAbortController.value.signal
    });
    
    if (response?.code === 0) {
      telemetryUploadStatusText.value = '上传成功';
      telemetryUploadResult.value = {
        success: true,
        message: `成功上传 ${selectedTelemetryFilesUpload.value.length} 个遥测数据文件`
      };
      ElMessage.success('遥测数据文件上传成功');
      // 将successFiles数组转换为逗号连接的字符串
      const anaDataLogFilePath = Array.isArray(response?.data?.successFiles) ? response.data.successFiles.join(',') : '';
      await  addAnaDataList('上传遥测数据文件',2,anaDataLogFilePath)
      // 1.5秒后关闭弹窗并重置
      setTimeout(() => {
        telemetryUploading.value = false;
        // 重新加载遥测文件列表
        loadTelemetryFiles();
      }, 1500);      
    } else {
      throw new Error(response?.msg || '上传失败');
    }
  } catch (error) {
    if (error.name !== 'AbortError') {
      telemetryUploadStatusText.value = '上传失败';
      telemetryUploadResult.value = {
        success: false,
        message: `上传失败: ${error.message}`
      };
      ElMessage.error(`上传失败: ${error.message}`);
    }
  } finally {
    telemetryUploading.value = false;
  }
};

// 取消遥测文件上传
const cancelTelemetryUpload = () => {
  if (telemetryAbortController.value) {
    telemetryAbortController.value.abort();
    telemetryAbortController.value = null;
  }
  telemetryUploading.value = false;
  telemetryUploadStatusText.value = '已取消上传';
};

// 重置遥测文件上传
const resetTelemetryUpload = () => {
  selectedTelemetryFilesUpload.value = [];
  telemetryUploadProgress.value = 0;
  telemetryUploadStatusText.value = '';
  telemetryUploadResult.value = null;
  
  // 清空上传引用
  if (telemetryUploadRef.value) {
    telemetryUploadRef.value.clearFiles();
  }
};

// 处理遥测文件上传关闭
const handleTelemetryUploadClose = () => {
  resetTelemetryUpload();
};

// 格式化文件大小显示
const formatTelemetryFileSize = (bytes) => {
  if (bytes === 0) return '0 Bytes';
  
  const k = 1024;
  const sizes = ['Bytes', 'KB', 'MB', 'GB'];
  const i = Math.floor(Math.log(bytes) / Math.log(k));
  
  return parseFloat((bytes / Math.pow(k, i)).toFixed(2)) + ' ' + sizes[i];
};

// 加载遥测文件
const loadTelemetryFiles = async () => {
  try {
    if (!currentRow.value.dataId) return;
    
    // 准备查询参数
    const params = {
      dataId: currentRow.value.dataId,
    };
    const telemetryResult = await telemetryDataListAPI.getTelemetryStoragePath(params);
    if (telemetryResult && telemetryResult.code === 0) {
      telemetryFiles.value = telemetryResult.data || [];
      // 重置选择
      selectedTelemetryFiles.value = [];
    } else {
      throw new Error(telemetryResult?.msg || '获取遥测文件失败');
    }
  } catch (error) {
    console.error("加载遥测文件时发生错误:", error);
    ElMessage.error(`加载遥测文件失败: ${error.message}`);
    telemetryFiles.value = [];
    selectedTelemetryFiles.value = [];
  }
};

// 切换遥测文件选择状态
const toggleTelemetryFileSelection = (fileName) => {
  const index = selectedTelemetryFiles.value.indexOf(fileName);
  if (index > -1) {
    selectedTelemetryFiles.value.splice(index, 1);
  } else {
    selectedTelemetryFiles.value.push(fileName);
  }
};

// 显示裁剪遥测数据弹窗
const openTelemetryCropDialog = () => {
  if (selectedTelemetryFiles.value.length === 0) {
    ElMessage.warning('请至少选择一个遥测数据文件');
    return;
  }
  
  // 解析选中的遥测文件内容
  parseSelectedTelemetryFiles().then(() => {
    // 计算所有选中文件的时间范围
    calculateTimeRange();
    // 打开弹窗
    showTelemetryCropDialog.value = true;
  });
};

// 计算所有选中文件的时间范围
const calculateTimeRange = () => {
  let min = Infinity;
  let max = -Infinity;
  
  // 遍历所有选中的文件数据
  for (const fileName of selectedTelemetryFiles.value) {
    const fileData = telemetryDataByFile.value[fileName];
    if (fileData && fileData.length > 0) {
      // 找到当前文件的最小和最大时间戳
      const fileMin = Math.min(...fileData.map(item => item.sysTime || 0));
      const fileMax = Math.max(...fileData.map(item => item.sysTime || 0));
      
      min = Math.min(min, fileMin);
      max = Math.max(max, fileMax);
    }
  }
  
  if (min !== Infinity && max !== -Infinity) {
    timeRangeMin.value = min;
    timeRangeMax.value = max;
    // 设置滑块初始值为整个范围
    timeSliderValues.value = [min, max];
    
    // 同时更新时间字符串
    updateTimeStrings(min, max);
  }
};

// 更新时间字符串
const updateTimeStrings = (startTimeStamp, endTimeStamp) => {
  cropStartTime.value = convertTimestampToTime(startTimeStamp);
  cropEndTime.value = convertTimestampToTime(endTimeStamp);
};

// 将时间戳转换为时间字符串(HH:mm:ss:SSS)
function convertTimestampToTime(timestamp) {
  const date = new Date(timestamp);
  const hours = String(date.getHours()).padStart(2, '0');
  const minutes = String(date.getMinutes()).padStart(2, '0');
  const seconds = String(date.getSeconds()).padStart(2, '0');
  const milliseconds = String(date.getMilliseconds()).padStart(3, '0');
  return `${hours}:${minutes}:${seconds}:${milliseconds}`;
}

// 格式化滑块提示信息
const formatSliderTooltip = (value) => {
  return convertTimestampToTime(value);
};

// 存储筛选后的遥测数据
const filteredTelemetryDataByFile = ref({});

// 处理滑块值变化
const handleSliderChange = (values) => {
  const [startTime, endTime] = values;
  updateTimeStrings(startTime, endTime);
  
  // 筛选每个文件的数据
  Object.keys(telemetryDataByFile.value).forEach(fileName => {
    const fileData = telemetryDataByFile.value[fileName];
    if (fileData && fileData.length > 0) {
      filteredTelemetryDataByFile.value[fileName] = fileData.filter(dataPoint => {
        const pointTime = dataPoint.sysTime || convertTimeToTimestamp(dataPoint.time);
        return pointTime >= startTime && pointTime <= endTime;
      });
    } else {
      filteredTelemetryDataByFile.value[fileName] = [];
    }
  });
};

// 初始化筛选数据
const initFilteredData = () => {
  Object.keys(telemetryDataByFile.value).forEach(fileName => {
    filteredTelemetryDataByFile.value[fileName] = [...(telemetryDataByFile.value[fileName] || [])];
  });
};

// 解析选中的遥测文件内容
const parseSelectedTelemetryFiles = async () => {
  try {
    for (const fileName of selectedTelemetryFiles.value) {
      // 如果已经解析过该文件，跳过
      if (telemetryDataByFile.value[fileName]) continue;
      const file = telemetryFiles.value.find(f => f.fileName === fileName);
      if (file) {
        const accessPath = file.accessPath || '';
        // 调用Electron API读取遥测文件内容
        const result = await window.electronAPI.readTelemetryFile({
          filePath: API_CONFIG.IMAGE_URL + accessPath
        });
        if (result.success && result.content) {
          const fileData = [];
          const fileContent = result.content;
          // 直接按行解析时间+值格式的文件
          const lines = fileContent.split('\n');
          
          lines.forEach(line => {
            line = line.trim();
            if (line) {
              // 只接受时间+值格式的文件（如：16:04:26:713 0）
              const timeValueMatch = line.match(/^(\d{2}:\d{2}:\d{2}:\d{3})\s+(\d+\.?\d*)$/);
              if (timeValueMatch) {
                // 解析时间格式：HH:mm:ss:SSS
                const timeStr = timeValueMatch[1];
                const value = parseFloat(timeValueMatch[2]);
                
                // 提取文件名作为参数名（去掉.txt后缀）
                const paramName = fileName.replace('.txt', '');
                
                // 创建符合曲线图要求的数据格式 - 添加x和y属性
                const dataPoint = {
                  sysTime: convertTimeToTimestamp(timeStr),
                  time: timeStr,
                  [paramName]: value,
                  x: timeStr,  // 使用时间作为x值
                  y: value     // 使用数据值作为y值
                };
                fileData.push(dataPoint);
              }
            }
          });
          
          // 按时间排序该文件的数据
          fileData.sort((a, b) => {
            const timeA = a.sysTime || a.time || a.timestamp || 0;
            const timeB = b.sysTime || b.time || b.timestamp || 0;
            return timeA - timeB;
          });
          
          // 存储该文件的数据
          telemetryDataByFile.value[fileName] = fileData;
          // 初始化筛选数据
          initFilteredData();
        }
      }      
    }
  } catch (error) {
    console.error("加载遥测数据时发生错误:", error);
    ElMessage.error("加载遥测数据失败");
  }
};

// 辅助函数：将时间字符串(HH:mm:ss:SSS)转换为时间戳
function convertTimeToTimestamp(timeStr) {
  const [hours, minutes, seconds, milliseconds] = timeStr.split(/[:.]/).map(Number);
  // 创建基于当前日期的时间对象，但使用解析的时分秒毫秒
  const date = new Date();
  date.setHours(hours, minutes, seconds, milliseconds);
  return date.getTime();
}

// 图表网格样式
const chartGridStyle = computed(() => {
  return {
    display: "grid",
    gridTemplateColumns: `repeat(${(windowLayout.value)}, 1fr)`,
    gap: "20px",
    padding: "16px",
    overflowY: "auto",
    flex: 1,
    minHeight: 0,
  };
});

// 确认裁剪遥测数据
const confirmCropTelemetry = async () => {
  // 验证时间格式
  if (!cropStartTime.value || !cropEndTime.value) {
    ElMessage.warning('请输入开始时间和结束时间');
    return;
  }
  
  // 验证时间格式是否符合 HH:mm:ss:SSS
  const timeRegex = /^\d{2}:\d{2}:\d{2}:\d{3}$/;
  if (!timeRegex.test(cropStartTime.value) || !timeRegex.test(cropEndTime.value)) {
    ElMessage.warning('时间格式不正确，请使用 HH:mm:ss:SSS 格式');
    return;
  }
  
  // 转换时间字符串为时间戳进行比较
  const startTimeStamp = convertTimeToTimestamp(cropStartTime.value);
  const endTimeStamp = convertTimeToTimestamp(cropEndTime.value);
  
  if (startTimeStamp >= endTimeStamp) {
    ElMessage.warning('开始时间不能大于或等于结束时间');
    return;
  }
  
  try {
    // 准备文件路径列表
    const filePathList = [];
    console.log('telemetryFiles.value:', telemetryFiles.value);
    // 对每个选中的文件进行裁剪操作
    for (const fileName of selectedTelemetryFiles.value) {
      const fileData = telemetryDataByFile.value[fileName];
      if (fileData && fileData.length > 0) {
        // 根据时间范围筛选数据
        const croppedData = fileData.filter(item => {
          const itemTimeStamp = item.sysTime;
          return itemTimeStamp >= startTimeStamp && itemTimeStamp <= endTimeStamp;
        });        
        console.log(`裁剪文件 ${fileName}，原数据点：${fileData.length}，裁剪后：${croppedData.length}`);
        
        // 获取文件路径
        const file = telemetryFiles.value.find(f => f.fileName === fileName);
        if (file) {
          filePathList.push({ path: file.absolutePath || fileName });
        }
      }
    }

    // 按要求格式封装参数
    const editTelemetryDataParams = {
      startDate: cropStartTime.value,
      endDate: cropEndTime.value,   
      filePathList: filePathList
    };
    
    console.log('发送的参数:', editTelemetryDataParams);
    
    // 调用API将裁剪后的数据保存到服务器
    const editTelemetryDataResult = await telemetryDataListAPI.editTelemetryData(editTelemetryDataParams);
    if (editTelemetryDataResult?.code === 0) {
      // 填充裁剪结果数据
      cropResultData.value = {
        timeRange: `${cropStartTime.value} - ${cropEndTime.value}`,
        telemetryFiles: [...selectedTelemetryFiles.value],
        newFilePath: editTelemetryDataResult.data
      };
      // 显示裁剪结果对话框
      showCropResultDialog.value = true;
    } else {
      ElMessage.error('裁剪遥测数据失败');
      throw new Error(editTelemetryDataResult?.msg || '裁剪遥测数据失败');
    }
    
    // 清空时间输入
    cropStartTime.value = '';
    cropEndTime.value = '';
  } catch (error) {
    console.error('裁剪遥测数据失败:', error);
    ElMessage.error('裁剪遥测数据失败');
  }
};

// 视频剪辑弹窗打开
const handleVideoEditOpen = () => {
  console.log('打开视频剪辑弹窗，选中的视频文件:', selectedVideoFile.value);
};
// 切换视频文件选择状态
const toggleVideoFileSelection = (fileName) => {
  const index = selectedVideoFiles.value.indexOf(fileName);
  if (index > -1) {
    selectedVideoFiles.value.splice(index, 1);
  } else {
    selectedVideoFiles.value.push(fileName);
  }
};

// 处理裁剪视频按钮点击
const handleCutVideoClick = () => {
  console.log('handleCutVideoClick 被调用');
  console.log('selectedVideoFiles.value:', selectedVideoFiles.value);
  if (selectedVideoFiles.value.length !== 1) {
    ElMessage.warning('请选择一个视频文件进行裁剪');
    return;
  }
  // 找到选中的视频文件对象
  const fileName = selectedVideoFiles.value[0];
  const videoFile = videoFiles.value.find(file => file.fileName === fileName);
  
  if (videoFile) {
    selectedVideoFile.value = videoFile;
    // 打开视频编辑弹窗
    showVideoEditDialog.value = true;
  }
};

// 处理拼接视频按钮点击
const handleConcatVideoClick = () => {
  if (selectedVideoFiles.value.length < 2) {
    ElMessage.warning('请至少选择两个视频文件进行拼接');
    return;
  }
  showVideoConcatDialog.value = true;
};

// 通用下载文件函数
const downloadFiles = async (selectedFiles, allFiles, fileType = '视频', videoFileType = null) => {
  if (selectedFiles.length === 0) {
    ElMessage.warning(`请至少选择一个${fileType}文件进行下载`);
    return;
  }
  
  // 计算选中文件的总大小
  let totalSize = 0;
  const filePaths = [];
  
  selectedFiles.forEach(fileName => {
    const file = allFiles.find(f => f.fileName === fileName);
    if (file) {
      // 计算总大小
      const sizeNum = parseFloat(file.fileSize);
      if (!isNaN(sizeNum)) {
        if (file.fileSizeUnit === 'KB') {
          totalSize += sizeNum * 1024; // 转换为字节
        } else if (file.fileSizeUnit === 'MB') {
          totalSize += sizeNum * 1024 * 1024; // 转换为字节
        } else if (file.fileSizeUnit === 'GB') {
          totalSize += sizeNum * 1024 * 1024 * 1024; // 转换为字节
        } else {
          totalSize += sizeNum; // 假设已经是字节
        }
      }
      if (file.absolutePath) {
        filePaths.push(file.absolutePath);
      }
    }
  });
  
  // 格式化总大小为MB显示
  const totalSizeMB = (totalSize / (1024 * 1024)).toFixed(2);
  
  try {
    // 弹出确认对话框
    await ElMessageBox.confirm(
      `确认要下载${selectedFiles.length}个${fileType}文件（${totalSizeMB}M）吗？`,
      '确认下载',
      {
        confirmButtonText: '确认',
        cancelButtonText: '取消',
        type: 'info'
      }
    );
    
    // 用户确认后，调用API进行下载
    console.log('下载文件路径:', filePaths);
    
    try {
      // 构建请求体，如果是视频类型则包含fileType参数
      const requestBody = {
        filePaths: filePaths
      };
      if (fileType === '视频' && videoFileType) {
        requestBody.fileType = videoFileType;
      }
      
      // 调用API进行下载
      const result = await fileAPI.downloadCompressionPackageFile(requestBody);
      
      if (result?.code === 0) {
        // 拼接文件路径并下载
        if (result?.msg) {
          const downloadUrl = videoPath.value + result.msg;
          // 创建下载链接
          const link = document.createElement('a');
          link.href = downloadUrl;
          link.download = ''; // 让浏览器自动从URL中推断文件名
          document.body.appendChild(link);
          link.click();
          // 清理
          document.body.removeChild(link);
          ElMessage.success(`${fileType}文件下载成功`);
        } else {
          ElMessage.error(`下载失败: 未返回下载路径！`);
        }
      } else {
        throw new Error(result?.msg || '下载失败');
      }
    } catch (apiError) {
      console.error('API调用失败:', apiError);
      throw apiError;
    }
  } catch (error) {
    if (error !== 'cancel' && error !== 'close') {
      console.error(`下载${fileType}文件失败:`, error);
      ElMessage.error(`下载失败: ${error.message}`);
    }
  }
};

// 处理下载视频按钮点击
const handleDownloadVideoClick = async () => {
  if (selectedVideoFiles.value.length === 0) {
    ElMessage.warning('请先选择视频文件');
    return;
  }
  // 显示视频类型选择对话框
  showVideoTypeDialog.value = true;
};

// 确认视频类型选择并开始下载
const confirmVideoTypeAndDownload = async () => {
  showVideoTypeDialog.value = false;
  await downloadFiles(selectedVideoFiles.value, videoFiles.value, '视频', selectedVideoType.value);
};

// 处理下载遥测数据按钮点击
const handleDownloadTelemetryClick = async () => {
  await downloadFiles(selectedTelemetryFiles.value, telemetryFiles.value, '遥测数据');
};

// 复用已有文件大小格式化函数
// formatFileSize 函数已在文件中定义，用于格式化文件大小显示

// 加载视频文件列表
const getVideoList = async () => {
  loading.value = true;
  try {
    console.log('currentRow.value.dataId:', currentRow.value.dataId);
    if (!currentRow.value.dataId) {
      videoFiles.value = [];
      selectedVideoFiles.value = [];
      loading.value = false;
      return;
    }
    
    const params = { dataId: currentRow.value.dataId };
    console.log('params:', params);
    const result = await videoDataAPI.getVideoList(params);
    if (result?.code === 0) {
      videoFiles.value = result.data || [];
      console.log('videoFiles.value:', videoFiles.value);
    } else {
      throw new Error(result?.msg || '获取视频文件失败');
    }
  } catch (error) {
    console.error("加载视频文件失败:", error);
    ElMessage.error(`加载视频文件失败: ${error.message}`);
    videoFiles.value = [];
  } finally {
    selectedVideoFiles.value = [];
    loading.value = false;
  }
};
// 格式化时间
const formatTime = (date) => {
  return date.toLocaleString('zh-CN', {
    year: 'numeric',
    month: '2-digit',
    day: '2-digit',
    hour: '2-digit',
    minute: '2-digit',
    second: '2-digit',
    hour12: false
  });
};

// 查看详情
const viewDetails = (item) => {
  detailsVisible.value = true;
  videoUrl.value=item
};

// 打开视频剪辑弹窗
const handleTopButtonClick = () => {
  showVideoEditDialog.value = true;
};

// 打开视频上传弹窗
const selectVideoFile = () => {
  showVideoFileDialog.value = true;
};

// 详情页跳转
const goToDetail = (row) => {
  // 保存当前页面状态到 sessionStorage
  const cacheData = {
    data: [...tableData.value],
    total: total.value,
    currentPage: currentPage.value,
    pageSize: pageSize.value,
    sortBy: sortBy.value,
    sortOrder: sortOrder.value
  };

  const cacheFilters = {
    startTime: startTime.value,
    endTime: endTime.value
  };

  sessionStorage.setItem('cachedData', JSON.stringify(cacheData));
  sessionStorage.setItem('cachedFilters', JSON.stringify(cacheFilters));
  sessionStorage.setItem('fromDataDetail', 'true');

  // 跳转到详情页
  sessionStorage.setItem('dataDetail', JSON.stringify(row));
  router.push({
    name: "DataDetail",
    params: {
      id: row.dataId
    }
  });
};

// 加载任务列表
const loadTaskList = async (resetPage = false) => {
  taskListLoading.value = true;
  try {
    if (resetPage) {
      taskCurrentPage.value = 1;
    }

    const params = {
      pageNum: taskCurrentPage.value,
      pageSize: taskPageSize.value,
      taskName: taskFilter.value.taskName || '',
      status: taskFilter.value.status || ''
    };

    const result = await taskAPI.getTaskList(params);

    if (result && result.code === 0) {
      taskList.value = result.rows || [];
      taskListTotal.value = result.total || 0;
    } else {
      throw new Error(result?.msg || '获取任务列表失败');
    }
  } catch (error) {
    console.error('加载任务列表失败:', error);
    ElMessage.error(`加载任务列表失败: ${error.message}`);
    taskList.value = [];
    taskListTotal.value = 0;
  } finally {
    taskListLoading.value = false;
  }
};

// 查询任务列表
const searchTaskList = async () => {
  await loadTaskList(true);
};

// 重置任务筛选
const resetTaskFilter = async () => {
  taskFilter.value = {
    taskName: '',
    status: ''
  };
  await loadTaskList(true);
};

// 任务分页处理
const handleTaskSizeChange = async (val) => {
  taskPageSize.value = val;
  taskCurrentPage.value = 1;
  await loadTaskList();
};

const handleTaskCurrentChange = async (val) => {
  taskCurrentPage.value = val;
  await loadTaskList();
};

// 任务行点击处理
const onTaskRowClick = (row) => {
  archiveForm.value.taskId = row.taskId;
  archiveForm.value.taskName = row.taskName;
};

// 清除任务选择
const clearTaskSelection = () => {
  archiveForm.value.taskId = "";
  archiveForm.value.taskName = "";
};

// 获取任务行样式类名
const getTaskRowClassName = ({ row }) => {
  return row.taskId === archiveForm.value.taskId ? 'selected-task-row' : '';
};

// 格式化任务时间
const formatTaskTime = (timeStr) => {
  if (!timeStr) return '-';
  return timeStr.split(':').slice(0, 3).join(':');
};

// 获取任务状态类型
const getTaskStatusType = (status) => {
  const statusMap = {
    '0': 'success',
    '1': 'danger'
  };
  return statusMap[status] || 'info';
};

// 获取任务状态文本
const getTaskStatusText = (status) => {
  const statusMap = {
    '0': '正常',
    '1': '停用'
  };
  return statusMap[status] || '未知';
};

// 归档按钮事件
const archiveData = (row) => {
  archiveForm.value = {
    taskId: "",
    taskName: "",
    dataId: row.dataId
  };

  taskFilter.value = {
    taskName: '',
    status: ''
  };
  taskCurrentPage.value = 1;
  taskPageSize.value = 10;

  showArchiveDialog.value = true;
  loadTaskList(true);
};

// 归档表单验证规则
const archiveRules = {
  taskId: [{ required: true, message: "请选择归档任务", trigger: "change" }],
  taskName: [{ required: true, message: "请选择归档任务", trigger: "change" }],
};

// 确认归档
const confirmArchive = async () => {
  try {
    await archiveFormRef.value.validate();
    archiveLoading.value = true;

    const archiveParams = {
      taskId: archiveForm.value.taskId,
      dataId: archiveForm.value.dataId
    };

    const result = await dataAPI.archiveData(archiveParams);

    if (result && result.code === 0) {
      archiveLoading.value = false;
      showArchiveDialog.value = false;
      ElMessage.success("归档成功");
      await loadCollectionData();
    } else {
      throw new Error(result?.msg || '归档失败');
    }

  } catch (error) {
    archiveLoading.value = false;
    console.error("归档失败:", error);
    ElMessage.error(`归档失败: ${error.message}`);
  }
};


// 表格选择变化
const handleSelectionChange = (selection) => {
  selectedRows.value = selection;
};

// 加载采集数据
const loadCollectionData = async () => {
  loading.value = true;
  try {
    const params = {
      pageNum: currentPage.value,
      pageSize: pageSize.value,
      startTime: startTime.value,
      endTime: endTime.value,
      orderByColumn: sortBy.value,
      isAsc: sortOrder.value === 'ascending' ? 'asc' : 'desc'
    };

    const result = await dataAPI.getDataList(params);

    if (result && result.code === 0) {
      tableData.value = result.rows || [];
      total.value = result.total || 0;
      ElMessage.success(`加载了 ${tableData.value.length} 条采集记录`);
    } else {
      throw new Error(result?.msg || '获取数据失败');
    }

  } catch (error) {
    console.error("加载采集数据失败:", error);
    ElMessage.error(`加载数据失败: ${error.message}`);
    tableData.value = [];
    total.value = 0;
  } finally {
    loading.value = false;
  }
};

// 搜索数据
const searchData = async () => {
  currentPage.value = 1;
  await loadCollectionData();
};

// 重置筛选
const resetFilter = async () => {
  startTime.value = "";
  endTime.value = "";
  currentPage.value = 1;
  await loadCollectionData();
  ElMessage.info("已重置筛选条件");
};

// 刷新数据
const refreshData = () => {
  loadCollectionData();
};

// 处理排序变化
const handleSortChange = ({ column, prop, order }) => {
  if (prop && order) {
    sortBy.value = prop;
    sortOrder.value = order;
  } else {
    sortBy.value = "startCollectTime";
    sortOrder.value = "descending";
  }
  loadCollectionData();
};

// 分页处理
const handleSizeChange = async (val) => {
  pageSize.value = val;
  currentPage.value = 1;
  await loadCollectionData();
};

const handleCurrentChange = async (val) => {
  currentPage.value = val;
  await loadCollectionData();
};

// 时间验证函数
const disabledStartDate = (time) => {
  const today = new Date();
  today.setHours(23, 59, 59, 999);

  if (endTime.value) {
    const endDate = new Date(endTime.value);
    return time.getTime() > Math.min(today.getTime(), endDate.getTime());
  }

  return time.getTime() > today.getTime();
};

const disabledEndDate = (time) => {
  const today = new Date();
  today.setHours(23, 59, 59, 999);

  if (startTime.value) {
    const startDate = new Date(startTime.value);
    return time.getTime() < startDate.getTime() || time.getTime() > today.getTime();
  }

  return time.getTime() > today.getTime();
};

// 时间变化处理函数
const onStartTimeChange = () => {
  if (startTime.value && endTime.value) {
    const startDate = new Date(startTime.value);
    const endDate = new Date(endTime.value);

    if (startDate.getTime() > endDate.getTime()) {
      endTime.value = "";
      ElMessage.warning("开始时间不能大于结束时间，已重置结束时间");
    }
  }
};

const onEndTimeChange = () => {
  if (startTime.value && endTime.value) {
    const startDate = new Date(startTime.value);
    const endDate = new Date(endTime.value);

    if (endDate.getTime() < startDate.getTime()) {
      endTime.value = "";
      ElMessage.warning("结束时间不能小于开始时间，请重新选择");
      return;
    }
  }
};

// 统一删除方法
const deleteData = async (rowOrIds = null) => {
  const isBatchDelete = !rowOrIds || Array.isArray(rowOrIds);
  const rowsToDelete = isBatchDelete ? selectedRows.value : [rowOrIds];
  const ids = rowsToDelete.map(row => row.dataId);

  if (isBatchDelete && ids.length === 0) {
    ElMessage.warning("请先选择要删除的数据");
    return;
  }

  try {
    let confirmMessage = "";
    if (isBatchDelete) {
      confirmMessage = `确定要批量删除 ${ids.length} 个采集数据吗？\n\n` +
          `⚠️ 此操作将同时删除：\n` +
          `• 数据库中的采集记录\n` +
          `• 本地采集目录（包含视频文件和遥测数据）\n\n` +
          `此操作不可恢复！`;
    } else {
      confirmMessage = `确定要删除采集数据吗？\n\n` +
          `序号: ${rowOrIds.dataId}\n` +
          `开始时间: ${rowOrIds.startCollectTime}\n` +
          `结束时间: ${rowOrIds.endCollectTime}\n` +
          `采集目录: ${rowOrIds.storagePath}\n\n` +
          `⚠️ 此操作将同时删除：\n` +
          `• 数据库中的采集记录\n` +
          `• 本地采集目录（包含视频文件和遥测数据）\n\n` +
          `此操作不可恢复！`;
    }

    const result = await ElMessageBox.confirm(
        confirmMessage,
        isBatchDelete ? "确认批量删除" : "确认删除",
        {
          confirmButtonText: "确定删除",
          cancelButtonText: "取消",
          type: "warning",
        }
    );

    if (result === "confirm") {
      const deleteResult = await dataAPI.deleteData(ids);

      if (deleteResult && deleteResult.code === 0) {
        const fileDeleteResults = [];

        for (const row of rowsToDelete) {
          if (row.storagePath) {
            try {
              let fullPath = row.storagePath;
              if (!fullPath.startsWith('./')) {
                fullPath = `./${fullPath}`;
              }

              if (!fullPath.startsWith('./collections/')) {
                fileDeleteResults.push({
                  dataId: row.dataId,
                  storagePath: row.storagePath,
                  success: false,
                  error: '路径格式不正确，应为 ./collections/时间戳 格式'
                });
                continue;
              }

              const fileDeleteResult = await window.electronAPI.deleteFile(fullPath);
              fileDeleteResults.push({
                dataId: row.dataId,
                storagePath: row.storagePath,
                fullPath: fullPath,
                success: fileDeleteResult.success,
                error: fileDeleteResult.error
              });
            } catch (fileError) {
              console.error(`删除采集目录时出错: ${row.storagePath}`, fileError);
              fileDeleteResults.push({
                dataId: row.dataId,
                storagePath: row.storagePath,
                fullPath: fullPath,
                success: false,
                error: fileError.message
              });
            }
          } else {
            fileDeleteResults.push({
              dataId: row.dataId,
              storagePath: null,
              fullPath: null,
              success: false,
              error: '没有存储路径信息'
            });
          }
        }

        const successfulFileDeletes = fileDeleteResults.filter(r => r.success).length;
        const failedFileDeletes = fileDeleteResults.filter(r => !r.success).length;

        let successMessage = "";
        if (isBatchDelete) {
          successMessage = `批量删除完成:\n` +
              `✅ 数据库记录: ${ids.length} 个\n` +
              `✅ 采集目录: ${successfulFileDeletes} 个`;
          if (failedFileDeletes > 0) {
            successMessage += `\n❌ 采集目录删除失败: ${failedFileDeletes} 个`;
          }
        } else {
          successMessage = `删除成功:\n` +
              `✅ 数据库记录已删除\n` +
              `✅ 采集目录已删除`;
        }

        ElMessage.success(successMessage);

        if (failedFileDeletes > 0) {
          const failedFiles = fileDeleteResults.filter(r => !r.success);
          console.warn('文件删除失败详情:', failedFiles);
          ElMessage.warning(`部分文件删除失败，请检查文件权限或手动删除`);
        }

        if (isBatchDelete) {
          selectedRows.value = [];
          if (dataTable.value) {
            dataTable.value.clearSelection();
          }
        }

        await loadCollectionData();
      } else {
        throw new Error(deleteResult?.msg || '数据库删除失败');
      }
    }
  } catch (error) {
    if (error === "cancel" || error === "close") {
      ElMessage.info("已取消删除");
    } else {
      console.error("删除操作失败:", error);
      ElMessage.error(`删除操作失败: ${error.message}`);
    }
  }
};

// 批量删除数据
const batchDeleteData = () => {
  deleteData();
};

// 视频上传 - 文件选择处理
const handleFileSelect = (uploadFile, uploadFiles) => {
  // 清空历史文件，仅保留最新选择的1个文件
  selectedFiles.value = [uploadFile.raw];
  const maxSize = 2 * 1024 * 1024 * 1024;
  if (uploadFile.size > maxSize) {
    selectedFiles.value = []; // 超限时清空
    ElMessage.error(`文件过大（${formatFileSize(uploadFile.size)}），请选择2GB以内的视频`);
  } else {
    ElMessage.info(`已选择文件：${uploadFile.name}（${formatFileSize(uploadFile.size)}）`);
  }
};

// 格式化文件大小
const formatFileSize = (bytes) => {
  if (bytes < 1024 * 1024) {
    return (bytes / 1024).toFixed(2) + " KB";
  } else if (bytes < 1024 * 1024 * 1024) {
    return (bytes / (1024 * 1024)).toFixed(2) + " MB";
  } else {
    return (bytes / (1024 * 1024 * 1024)).toFixed(2) + " GB";
  }
};

// 提交上传视频
const submitUpload = async () => {
  if (!selectedFiles.value.length) {
    ElMessage.warning("请先选择视频文件");
    return;
  }
  const file = selectedFiles.value[0];
  const maxSize = 2 * 1024 * 1024 * 1024; // 2GB 限制
  if (file.size > maxSize) {
    ElMessage.error(`文件过大（${formatFileSize(file.size)}），请选择2GB以内的视频`);
    return;
  }

  // 初始化上传状态
  uploading.value = true;
  uploadProgress.value = 0;
  uploadStatusText.value = `正在上传：${file.name}（${formatFileSize(file.size)}）`;
  uploadResult.value = null;

  // 构建 FormData
  const data = new FormData();
  data.append('file', file);
// 确保路径参数是字符串类型
  const storagePath = String(currentRow.value.storagePath || '');
  data.append('path', storagePath);
  // 创建中断控制器
  abortController.value = new AbortController();
  try {
    // 发起上传请求
    const res = await request.upload(
        '/system/videoSave/upload',
        data,
        {
          onUploadProgress: (e) => {
            if (e.lengthComputable) {
              uploadProgress.value = Math.round((e.loaded / e.total) * 100);
              uploadStatusText.value = `上传中：${uploadProgress.value}%（${formatFileSize(e.loaded)}/${formatFileSize(e.total)}）`;
            }
          },
          signal: abortController.value.signal
        }
    );
    // 上传成功处理
    if (res.code === 0) {
      uploadProgress.value = 100;
      uploadStatusText.value = "上传完成";
      uploadResult.value = { success: true, message: "视频上传成功！" };
      ElMessage.success("视频上传成功");
      uploadVideoUrl.value=res.data;
      // 将successFiles数组转换为逗号连接的字符串
      const anaDataLogFilePath = Array.isArray(res?.data?.successFiles) ? res.data.successFiles.join(',') : '';
      await  addAnaDataList('上传视频',1,anaDataLogFilePath)
      // 1.5秒后关闭弹窗并重置
      setTimeout(() => {
        showVideoFileDialog.value = false;
      //  resetUpload();
        getVideoList();
      }, 1500);
    } else {
      throw new Error(res.msg || "上传失败：后端处理异常");
    }
  } catch (err) {
    // 上传失败处理（排除“用户取消”的错误）
    if (err.name !== 'AbortError') {
      uploadStatusText.value = "上传失败";
      uploadResult.value = { success: false, message: err.message || "上传超时或网络异常" };
      ElMessage.error(`上传失败：${err.message}`);
      console.error("视频上传错误：", err);
    }
  } finally {
    uploading.value = false;
  }
};

//添加用户操作记录方法
const addAnaDataList = async (operation,operationType,filePath) => {
  loading.value = true;
  try {
    const params = {
      dataId: currentRow.value.dataId,
      operation: operation,
      operationType: operationType,
      filePath: filePath,
    };

    const result = await dataAPI.getAddAnaDataList(params);

    if (result && result.code === 0) {
      tableData.value = result.rows || [];
      total.value = result.total || 0;
      ElMessage.success(`加载了 ${tableData.value.length} 条采集记录`);
    } else {
      throw new Error(result?.msg || '获取数据失败');
    }

  } catch (error) {
    console.error("加载采集数据失败:", error);
    ElMessage.error(`加载数据失败: ${error.message}`);
    tableData.value = [];
    total.value = 0;
  } finally {
    loading.value = false;
  }
};
// 取消上传视频
const cancelUpload = () => {
  if (abortController.value) {
    abortController.value.abort();
    uploadStatusText.value = "已取消上传";
    uploading.value = false;
    ElMessage.info("上传已取消");
  }
};

// 重置上传视频状态
const resetUpload = () => {
  selectedFiles.value = [];
  uploadProgress.value = 0;
  uploadStatusText.value = "";
  uploadResult.value = null;
  if (videoUploadRef.value) {
    videoUploadRef.value.clearFiles();
  }
};

// 关闭上传视频弹窗时重置状态
const handleVideoUploadClose = () => {
  if (uploading.value && abortController.value) {
    abortController.value.abort();
    ElMessage.info("上传已取消（弹窗已关闭）");
  }
  resetUpload();
};

// 页面挂载时加载数据
onMounted(async () => {
  console.log('DataManagement onMounted 被调用');

  // 检查是否从详情页返回
  const isFromDetail = sessionStorage.getItem('fromDataDetail') === 'true';
  const isFromMenu = sessionStorage.getItem('isFromMenu') === 'true';

  // 清除标记
  sessionStorage.removeItem('fromDataDetail');
  sessionStorage.removeItem('isFromMenu');

  if (isFromDetail) {
    // 从详情页返回，尝试恢复缓存的数据和状态
    const cachedDataStr = sessionStorage.getItem('cachedData');
    const cachedFiltersStr = sessionStorage.getItem('cachedFilters');

    if (cachedDataStr && cachedFiltersStr) {
      const cachedData = JSON.parse(cachedDataStr);
      const cachedFilters = JSON.parse(cachedFiltersStr);

      tableData.value = cachedData.data;
      total.value = cachedData.total;
      currentPage.value = cachedData.currentPage;
      pageSize.value = cachedData.pageSize;
      startTime.value = cachedFilters.startTime || null;
      endTime.value = cachedFilters.endTime || null;
      sortBy.value = cachedData.sortBy || 'startCollectTime';
      sortOrder.value = cachedData.sortOrder || 'descending';

      // 清除缓存
      sessionStorage.removeItem('cachedData');
      sessionStorage.removeItem('cachedFilters');
    } else {
      await Promise.all([
        loadCollectionData()
      ]);
    }
  } else {
    // 首次加载或从菜单进入，重新加载数据
    await Promise.all([
      loadCollectionData()
    ]);
  }
});
</script>

<style scoped>
.data-management {
  padding: 0 10px;
  height: 100vh;
  display: flex;
  flex-direction: column;
  overflow: hidden;
}

.filter-bar {
  background: white;
  padding: 20px;
  border-radius: 8px;
  margin-bottom: 20px;
  box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
  flex-shrink: 0;
}

.time-filter {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 10px;
}

.filter-label {
  font-weight: 500;
  color: #333;
  white-space: nowrap;
}

.table-section {
  background: white;
  border-radius: 8px;
  box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
  flex: 1;
  display: flex;
  flex-direction: column;
  overflow: hidden;
}

.table-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 20px;
  border-bottom: 1px solid #f0f0f0;
  flex-shrink: 0;
}

.table-header h3 {
  margin: 0;
  font-size: 18px;
  font-weight: 600;
  color: #333;
}

/* 视频类型选择对话框样式 */
.video-type-dialog-content {
  padding: 20px 0;
}

.video-type-radio-group {
  display: flex;
  flex-direction: column;
  gap: 12px;
}

.video-type-radio-group .el-radio {
  margin-right: 0;
  height: 36px;
  display: flex;
  align-items: center;
  padding: 8px 12px;
  border-radius: 6px;
  transition: all 0.3s ease;
}

.video-type-radio-group .el-radio:hover {
  background-color: #f5f7fa;
}

.video-type-radio-group .el-radio.is-checked {
  background-color: #e6f7ff;
  border: 1px solid #409eff;
}

.table-controls {
  display: flex;
  gap: 10px;
}

.table-container {
  flex: 1;
  overflow: hidden;
  padding: 0 20px;
}

.time-cell {
  display: flex;
  align-items: center;
  gap: 5px;
  justify-content: center;
}

.action-buttons {
  display: flex;
  gap: 5px;
  justify-content: center;
}

.pagination-container {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 20px;
  border-top: 1px solid #f0f0f0;
  flex-shrink: 0;
}

.pagination-info {
  color: #666;
  font-size: 14px;
}

.path-cell {
  font-family: 'Courier New', monospace;
  font-size: 12px;
  color: #666;
  word-break: break-all;
}

/* 归档弹窗样式 */
.archive-dialog-content {
  display: flex;
  flex-direction: column;
  gap: 20px;
}

.task-filter-section {
  background: #f8f9fa;
  padding: 16px;
  border-radius: 8px;
  border: 1px solid #e9ecef;
}

.task-filter-section h4 {
  margin: 0 0 12px 0;
  font-size: 14px;
  font-weight: 600;
  color: #333;
}

.filter-controls {
  display: flex;
  gap: 12px;
  align-items: center;
  flex-wrap: wrap;
}

.task-list-section {
  border: 1px solid #e9ecef;
  border-radius: 8px;
  overflow: hidden;
}

.task-list-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 12px 16px;
  background: #f8f9fa;
  border-bottom: 1px solid #e9ecef;
  font-size: 14px;
  font-weight: 500;
}

.task-list-container {
  max-height: 300px;
  overflow: hidden;
}

.task-pagination {
  display: flex;
  justify-content: center;
  align-items: center;
  padding: 12px 16px;
  background: #f8f9fa;
  border-top: 1px solid #e9ecef;
}

.task-name-cell {
  display: flex;
  align-items: center;
  gap: 8px;
}

.task-icon {
  color: #409eff;
  font-size: 16px;
}

.time-text {
  font-family: 'Courier New', monospace;
  font-size: 12px;
  color: #666;
}

.selected-task-row {
  background-color: #e6f7ff !important;
}

.selected-task-row:hover {
  background-color: #bae7ff !important;
}

.archive-form-section {
  background: #f8f9fa;
  padding: 16px;
  border-radius: 8px;
  border: 1px solid #e9ecef;
}

.archive-form-section h4 {
  margin: 0 0 12px 0;
  font-size: 14px;
  font-weight: 600;
  color: #333;
}

.selected-icon {
  color: #67c23a;
  font-size: 16px;
}

.top-button {
  padding: 8px 16px;
  background-color: #2196f3;
  color: white;
  border: none;
  border-radius: 4px;
  cursor: pointer;
  font-size: 14px;
}

.top-button:hover {
  background-color: #0b7dda;
}

.top-button:disabled {
  background-color: #cccccc;
  color: #999999;
  cursor: not-allowed;
  opacity: 0.6;
}

.timeline-container {
  margin-top: 60px;
}

.timeline-container h1 {
  text-align: center;
  color: #333;
  margin-bottom: 30px;
}

.timeline {
  position: relative;
  padding-left: 30px;
}

.timeline::before {
  content: '';
  position: absolute;
  left: 10px;
  top: 0;
  bottom: 0;
  width: 2px;
  background-color: #e0e0e0;
}

.timeline-item {
  position: relative;
  margin-bottom: 20px;
}

.timeline-dot {
  position: absolute;
  left: -30px;
  top: 5px;
  width: 20px;
  height: 20px;
  border-radius: 50%;
  background-color: #2196f3;
}

.timeline-content {
  padding: 15px;
  background-color: #f9f9f9;
  border-radius: 6px;
  box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
}

.timeline-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 8px;
}

.editor-name {
  font-weight: bold;
  color: #333;
  font-size: 15px;
}

.action-type {
  color: #666;
  flex-grow: 1;
  margin-left: 15px;
  font-size: 15px;
}

.view-button {
  padding: 4px 10px;
  background-color: #2196F3;
  color: white;
  border: none;
  border-radius: 3px;
  cursor: pointer;
  font-size: 13px;
}

.view-button:hover {
  background-color: #0b7dda;
}

.timeline-time {
  color: #888;
  font-size: 14px;
}

.timeline-details {
  margin-top: 10px;
  padding: 10px;
  background-color: #fff;
  border-radius: 4px;
  border-left: 3px solid #2196F3;
}

/* 视频上传弹窗样式 */
.video-upload-container {
  padding: 10px 0;
}

.file-select-section {
  /*text-align: center;*/
  padding: 20px 0;
}

.upload-tip {
  color: #666;
  font-size: 12px;
}

.upload-progress-section {
  padding: 20px 0;
}

.upload-status {
  color: #666;
}

/* 遥测文件选择区域样式 */
.file-selection-section {
  background: white;
  border-radius: 8px;
  border: 1px solid #e8e8e8;
  margin-bottom: 16px;
  padding: 16px;
}

.file-selection-section .section-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 12px;
}

.file-selection-section .section-header h3 {
  margin: 0;
  font-size: 16px;
  font-weight: 500;
}

.file-selection-section .file-count {
  color: #606266;
  font-size: 14px;
}

/* 数据网格样式 */
.data-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
  gap: 12px;
}

.data-card {
  border: 1px solid #e8e8e8;
  border-radius: 8px;
  padding: 12px;
  cursor: pointer;
  transition: all 0.3s ease;
  display: flex;
  align-items: flex-start;
  gap: 12px;
  background: white;
  position: relative;
}

/* 调整标签在卡片中的位置 */
.data-card .el-tag {
  position: absolute;
  top: 6px;
  right: 6px;
  z-index: 1;
}

.data-card:hover {
  border-color: #409eff;
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
}

.data-card.selected {
  border-color: #409eff;
  box-shadow: 0 0 0 2px rgba(64, 158, 255, 0.2);
}

.card-checkbox {
  flex-shrink: 0;
}

.card-checkbox input[type="checkbox"] {
  display: none;
}

.card-checkbox .custom-checkbox {
  display: inline-block;
  width: 20px;
  height: 20px;
  border: 1px solid #dcdfe6;
  border-radius: 4px;
  position: relative;
  cursor: pointer;
  transition: all 0.3s ease;
}

.card-checkbox input[type="checkbox"]:checked + .custom-checkbox {
  background-color: #409eff;
  border-color: #409eff;
}

.card-checkbox input[type="checkbox"]:checked + .custom-checkbox::after {
  content: "";
  position: absolute;
  left: 6px;
  top: 3px;
  width: 6px;
  height: 10px;
  border: solid white;
  border-width: 0 2px 2px 0;
  transform: rotate(45deg);
}

.card-content {
  flex: 1;
  min-width: 0;
}

.data-name {
  margin: 0 0 4px 0;
  font-size: 14px;
  font-weight: 500;
  color: #303133;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.file-size {
  margin: 0;
  font-size: 13px;
  color: #909399;
}

/* 裁剪遥测数据弹窗样式 */
.telemetry-crop-container {
  font-size: 14px;
}

.crop-toolbar {
  background: #f5f7fa;
  padding: 12px 16px;
  border-radius: 6px;
}

.chart-info {
  color: #606266;
  font-size: 14px;
}

.toolbar-label {
  color: #606266;
  font-size: 14px;
}

.chart-section {
  background: white;
  border-radius: 8px;
  border: 1px solid #e8e8e8;
  display: flex;
  flex-direction: column;
  min-height: 0;
}

.chart-grid {
  flex: 1;
  overflow-y: auto;
}

.chart-item {
  border: 1px solid #e8e8e8;
  border-radius: 8px;
  background: white;
  overflow: hidden;
  height: 300px;
}

.chart-item-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 12px 16px;
  background: #f5f7fa;
  border-bottom: 1px solid #e8e8e8;
}

.chart-file-name {
  font-weight: 500;
  color: #303133;
  font-size: 14px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  flex: 1;
}

.chart-data-count {
  color: #606266;
  font-size: 13px;
  margin-left: 12px;
}

.chart-container {
  padding: 16px;
  min-height: 300px;
}

.no-telemetry {
  text-align: center;
  padding: 40px 30px;
  background: linear-gradient(135deg, #f8f9fa 0%, #e9ecef 100%);
  border-radius: 12px;
  margin: 16px;
  min-height: 250px;
  display: flex;
  align-items: center;
  justify-content: center;
}

.time-selection {
  padding: 12px 0;
}

.upload-result-section {
  padding: 30px 0;
  text-align: center;
}

.result-icon {
  font-size: 48px;
  margin: 0 auto;
  width: 60px;
  height: 60px;
  border-radius: 50%;
  display: flex;
  align-items: center;
  justify-content: center;
}

.result-icon.success {
  color: #67c23a;
  background-color: #f0f9eb;
}

.result-icon.error {
  color: #f56c6c;
  background-color: #fef0f0;
}

.result-message {
  color: #333;
}

.data-management-tab-container .el-tab-pane{
  min-height: 400px;
}

/* 裁剪结果对话框样式 */
.crop-result-content {
  padding: 10px 0;
}

.result-item {
  margin-bottom: 16px;
  display: flex;
  flex-direction: column;
}

.result-label {
  font-weight: 500;
  color: #606266;
  margin-bottom: 8px;
}

.result-value {
  color: #303133;
  word-break: break-all;
}

.file-list {
  margin: 0;
  padding-left: 20px;
}

.file-list li {
  margin-bottom: 4px;
}

/* 遥测数据上传对话框样式 */
.telemetry-upload-container {
  min-height: 200px;
}

.selected-file-list {
  max-height: 200px;
  overflow-y: auto;
  border: 1px solid #e8e8e8;
  border-radius: 4px;
  padding: 10px;
}

.file-item {
  display: flex;
  align-items: center;
  padding: 5px 0;
  border-bottom: 1px solid #f0f0f0;
}

.file-item:last-child {
  border-bottom: none;
}

.file-name {
  flex: 1;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.file-size {
  color: #909399;
  font-size: 12px;
  margin-left: 10px;
}

/* 视频文件列表样式 */
.video-file-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(250px, 1fr));
  gap: 16px;
  margin: 16px 0;
}

.video-file-card {
  border: 1px solid #e8e8e8;
  border-radius: 4px;
  padding: 12px;
  cursor: pointer;
  transition: all 0.3s ease;
  background-color: #fff;
}

.video-file-card:hover {
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
  transform: translateY(-2px);
}

.video-file-card.selected {
  border-color: #2196f3;
  background-color: #e3f2fd;
}

.video-file-info {
  display: flex;
  align-items: center;
  justify-content: space-between;
}

.video-select-checkbox {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 20px;
  height: 20px;
  border: 1px solid #dcdfe6;
  border-radius: 4px;
  background-color: #fff;
  margin-right: 10px;
}

.video-select-checkbox.checked {
  background-color: #2196f3;
  border-color: #2196f3;
  color: white;
}

.video-file-content {
  flex: 1;
}

.el-dialog__body{
  padding: 0;
  overflow: hidden;
}
</style>
